package com.suning.sawp.service.impl.mainpushnew;

import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.math.NumberUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.suning.sawp.constants.MainPushConstants;
import com.suning.sawp.dto.common.QueryResult;
import com.suning.sawp.dto.common.ReturnMsg;
import com.suning.sawp.exception.SawpException;
import com.suning.sawp.intf.dao.mainpushnew.MainPushTaskHqHandleDao;
import com.suning.sawp.intf.dao.mainpushnew.MainPushTaskHqViewDao;
import com.suning.sawp.intf.mainpushnew.MainPushTaskHqViewService;
import com.suning.sawp.po.mainpushnew.HqTask;
import com.suning.sawp.service.util.BigDecimalUtils;
import com.suning.sawp.service.util.DateUtils;
import com.suning.sawp.vo.mainpushnew.BiAreaTaskProgressVo;
import com.suning.sawp.vo.mainpushnew.BiHqTaskProgressVo;
import com.suning.sawp.vo.mainpushnew.BiModelProgressVo;
import com.suning.sawp.vo.mainpushnew.HqTaskVo;

/**
 * 
 * 总部主推任务查看接口实现<br>
 *
 * @author 14060886 祝翔龙
 */
@Service
public class MainPushTaskHqViewServiceImpl implements MainPushTaskHqViewService {

    @Autowired
    private MainPushTaskHqViewDao mainPushTaskHqViewDao;
    @Autowired
    private MainPushTaskHqHandleDao mainPushTaskHqHandleDao;
    
    @Override
    public ReturnMsg<BiHqTaskProgressVo> queryHqTaskProgress(Long hqTaskId) {
        BiHqTaskProgressVo hqTaskProgressInfo = mainPushTaskHqViewDao.selectHqTaskProgress(hqTaskId);
        if(null == hqTaskProgressInfo){
            throw new SawpException("未查询到该总部任务");
        }
        hqTaskProgressInfo.setRate(hqTaskProgressInfo.getRate().multiply(new BigDecimal(100)));
        hqTaskProgressInfo.setMonth(DateUtils.getFormatDay(hqTaskProgressInfo.getMonth(), 
                DateUtils.YYYYMM_PATTERN, DateUtils.DEFAULT_MONTH_PATTERN).replace("-", "年") + "月");
        hqTaskProgressInfo.setSaleNumRate(getCompleteRate(hqTaskProgressInfo.getTargetSaleNum(), hqTaskProgressInfo.getCurrentSaleNum()));
        hqTaskProgressInfo.setSaleAmountRate(getSaleRate(hqTaskProgressInfo.getCateSaleAmount(), hqTaskProgressInfo.getCurrentSaleAmount()));
        hqTaskProgressInfo.setCurrentSaleNum(defaultZero(hqTaskProgressInfo.getCurrentSaleNum()));
        hqTaskProgressInfo.setCurrentSaleAmount(defaultZero(hqTaskProgressInfo.getCurrentSaleAmount()));
        hqTaskProgressInfo.setCateSaleAmount(defaultZero(hqTaskProgressInfo.getCateSaleAmount()));
        ReturnMsg<BiHqTaskProgressVo> result = new ReturnMsg<BiHqTaskProgressVo>();
        result.setRetFlag(ReturnMsg.SUCCESS);
        result.setData(hqTaskProgressInfo);
        return result;
    }

    @Override
    public ReturnMsg<QueryResult<BiAreaTaskProgressVo>> queryAreaTaskProgress(Long hqTaskId, String queryParam, Map<String, Integer> pageParams) {
        Integer count = mainPushTaskHqViewDao.countAreaTaskProgress(hqTaskId, queryParam);
        List<BiAreaTaskProgressVo> areaTaskProgressInfo = mainPushTaskHqViewDao.selectAreaTaskProgress(hqTaskId, queryParam, pageParams);
        if(CollectionUtils.isEmpty(areaTaskProgressInfo)){
            throw new SawpException("未查询到大区完成情况");
        }
        ReturnMsg<QueryResult<BiAreaTaskProgressVo>> result = new ReturnMsg<QueryResult<BiAreaTaskProgressVo>>();
        QueryResult<BiAreaTaskProgressVo> pageResult = new QueryResult<BiAreaTaskProgressVo>();
        pageResult.setTotalSize(count);
        pageResult.setRecords(getAreaTaskProgressResult(mergeDataByType(areaTaskProgressInfo), pageParams.get("start"), hqTaskId));
        result.setRetFlag(ReturnMsg.SUCCESS);
        result.setData(pageResult);
        return result;
    }
 
    @Override
    public ReturnMsg<List<BiModelProgressVo>> queryModelProgress(Long hqTaskId, String disCode) {
        List<BiModelProgressVo> modelProgressInfo = mainPushTaskHqViewDao.selectModelProgress(hqTaskId, disCode);
        if(CollectionUtils.isEmpty(modelProgressInfo)){
            throw new SawpException("未查询到款数完成情况");
        }
        HqTaskVo hqTask = mainPushTaskHqHandleDao.selectHqTaskInfoById(hqTaskId);
        //查询品类总销售
        BigDecimal cateSaleAmount = mainPushTaskHqViewDao.selectCateSaleAmountByCode(hqTask.getCateCode(), hqTask.getMonth(), null);
        for(BiModelProgressVo modelProgress : modelProgressInfo){
            //B2完成率记为0
            if(MainPushConstants.PUSH_TYPE_B2.equals(modelProgress.getTaskType())){
                modelProgress.setCompleteRate(BigDecimal.ZERO);
            }else{
                modelProgress.setCompleteRate(getCompleteRate(modelProgress.getTargetNum(), modelProgress.getSaleNum()));
            }
            modelProgress.setSaleAmount(defaultZero(modelProgress.getSaleAmount()));
            modelProgress.setSaleNum(defaultZero(modelProgress.getSaleNum()));
            modelProgress.setSaleRate(getSaleRate(cateSaleAmount, modelProgress.getSaleAmount()));
        }
        ReturnMsg<List<BiModelProgressVo>> result = new ReturnMsg<List<BiModelProgressVo>>();
        result.setRetFlag(ReturnMsg.SUCCESS);
        result.setData(modelProgressInfo);
        return result;
    }
    
    @Override
    public List<BiAreaTaskProgressVo> queryAreaTaskProgress4Export(Long hqTaskId) {
        List<BiAreaTaskProgressVo> areaTaskProgressInfo = mainPushTaskHqViewDao.selectAreaTaskProgress(hqTaskId, StringUtils.EMPTY, new HashMap<String, Integer>());
        if(CollectionUtils.isEmpty(areaTaskProgressInfo)){
            throw new SawpException("未查询到大区完成情况");
        }
        return getAreaTaskProgressResult(mergeDataByType(areaTaskProgressInfo), NumberUtils.INTEGER_ONE, hqTaskId);
    }
    
    /**
     * 
     * 功能描述: 按主推类型合并大区数据<br>
     *
     * @param areaTaskProgressInfo
     */
    private Map<String, List<BiAreaTaskProgressVo>> mergeDataByType(List<BiAreaTaskProgressVo> areaTaskProgressInfo){
        Map<String, List<BiAreaTaskProgressVo>> areaTaskProgressMap = new HashMap<String, List<BiAreaTaskProgressVo>>();
        for(BiAreaTaskProgressVo areaProgress : areaTaskProgressInfo){
            String disCode = areaProgress.getDisCode();
            List<BiAreaTaskProgressVo> areaProgressList = areaTaskProgressMap.get(disCode);
            if(CollectionUtils.isEmpty(areaProgressList)){
                List<BiAreaTaskProgressVo> newList = new ArrayList<BiAreaTaskProgressVo>();
                newList.add(areaProgress);
                areaTaskProgressMap.put(disCode, newList);
            }else{
                areaProgressList.add(areaProgress);
                //Key大区编码 Value按主推类型分类的大区主推任务完成情况
                areaTaskProgressMap.put(disCode, areaProgressList);
            }
        }
        return areaTaskProgressMap;
    }
    
    /**
     * 
     * 功能描述: 获得大区任务完成进度结果<br>
     *
     * @param areaTaskProgressMap
     * @return
     */
    private List<BiAreaTaskProgressVo> getAreaTaskProgressResult(Map<String, List<BiAreaTaskProgressVo>> areaTaskProgressMap, Integer pageNo, 
            Long hqTaskId){
        List<BiAreaTaskProgressVo> result = new ArrayList<BiAreaTaskProgressVo>();
        HqTaskVo hqTask = mainPushTaskHqHandleDao.selectHqTaskInfoById(hqTaskId);
        //第一页增加合计行
        if(pageNo == NumberUtils.INTEGER_ZERO){
            //查询大区合计
            List<BiAreaTaskProgressVo> areaTaskProgressTotalInfo = mainPushTaskHqViewDao.selectTotalAreaTaskProgress(hqTaskId);
            result.add(setAreaTaskProgressInfo(areaTaskProgressTotalInfo, hqTask, StringUtils.EMPTY));
        }
        for(Map.Entry<String, List<BiAreaTaskProgressVo>> entry : areaTaskProgressMap.entrySet()){
            result.add(setAreaTaskProgressInfo(entry.getValue(), hqTask, entry.getKey()));
        }
        return result;
    }
    
    /**
     * 
     * 功能描述: 组装大区任务完成情况数据<br>
     *
     * @param valueList
     * @param hqTask
     * @param disCode
     * @return
     */
    private BiAreaTaskProgressVo setAreaTaskProgressInfo(List<BiAreaTaskProgressVo> valueList, HqTaskVo hqTask, String disCode){
        if(CollectionUtils.isEmpty(valueList)){
            return getEmptyTotalTaskProgress(hqTask);
        }
        BiAreaTaskProgressVo item = new BiAreaTaskProgressVo();
        for(BiAreaTaskProgressVo value : valueList){
            if(StringUtils.isEmpty(value.getPushType())){
                item.setSaleNumA(NumberUtils.INTEGER_ZERO);
                item.setSaleAmountA(BigDecimal.ZERO);
                item.setSaleNumB(NumberUtils.INTEGER_ZERO);
                item.setSaleAmountB(BigDecimal.ZERO);
                item.setSaleNumB2(NumberUtils.INTEGER_ZERO);
                item.setSaleAmountB2(BigDecimal.ZERO);
                item.setTargetNumA(defaultZero(mainPushTaskHqViewDao.selectTargetNumByDisAndType(hqTask.getId(), 
                        disCode, MainPushConstants.PUSH_TYPE_A)));
                item.setTargetNumB(defaultZero(mainPushTaskHqViewDao.selectTargetNumByDisAndType(hqTask.getId(), 
                        disCode, MainPushConstants.PUSH_TYPE_B)));
            }else if(value.getPushType().equals(MainPushConstants.PUSH_TYPE_A)){
                item.setSaleNumA(value.getSaleNum());
                item.setSaleAmountA(defaultZero(value.getSaleAmount()));
                //查询A类目标台数
                item.setTargetNumA(defaultZero(mainPushTaskHqViewDao.selectTargetNumByDisAndType(hqTask.getId(), 
                        disCode, MainPushConstants.PUSH_TYPE_A)));
            }else if(value.getPushType().equals(MainPushConstants.PUSH_TYPE_B)){
                item.setSaleNumB(value.getSaleNum());
                item.setSaleAmountB(defaultZero(value.getSaleAmount()));
                //查询B类目标台数
                item.setTargetNumB(defaultZero(mainPushTaskHqViewDao.selectTargetNumByDisAndType(hqTask.getId(), 
                        disCode, MainPushConstants.PUSH_TYPE_B)));
            }else if(value.getPushType().equals(MainPushConstants.PUSH_TYPE_B2)){
                item.setSaleNumB2(value.getSaleNum());
                item.setSaleAmountB2(defaultZero(value.getSaleAmount()));
            }
            item.setDisCode(disCode);
            item.setDisName(value.getDisName());
        }
        item.setCompleteRate(getCompleteRate(item));
        //查询品类销售额
        BigDecimal cateSaleAmount = mainPushTaskHqViewDao.selectCateSaleAmountByCode(hqTask.getCateCode(), hqTask.getMonth(), disCode);
        item.setCateSaleAmount(defaultZero(cateSaleAmount));
        item.setSaleRate(getSaleRate(cateSaleAmount, defaultZero(item.getSaleAmountA()).add(defaultZero(item.getSaleAmountB()))
                .add(defaultZero(item.getSaleAmountB2()))));
        item.setRate(hqTask.getRate());
        return item;
    }
    
    /**
     * 
     * 功能描述: 得到销售占比 = 主推销售额 / 品类销售额<br>
     *
     * @param cateSaleAmount 品类销售额
     * @param saleAmount 主推销售额
     * @return
     */
    private BigDecimal getSaleRate(BigDecimal cateSaleAmount, BigDecimal saleAmount){
        return BigDecimalUtils.halfUpThreeDecimal(
                (null == cateSaleAmount || cateSaleAmount.compareTo(BigDecimal.ZERO) == 0 || null == saleAmount) 
                    ? BigDecimal.ZERO : (saleAmount.divide(cateSaleAmount, 3, BigDecimal.ROUND_HALF_UP))).multiply(BigDecimal.valueOf(100));
    }
    
    /**
     * 
     * 功能描述: 得到完成率 = 主推销售台数/目标台数<br>
     *
     * @param targetNum 目标台数
     * @param saleNum 主推销售台数
     * @return
     */
    private BigDecimal getCompleteRate(Integer targetNum, Integer saleNum){
        return BigDecimalUtils.halfUpThreeDecimal((null == targetNum || targetNum == 0 || null == saleNum) ? BigDecimal.ZERO 
                : BigDecimal.valueOf(saleNum).divide(BigDecimal.valueOf(targetNum), 3, BigDecimal.ROUND_HALF_UP)).multiply(BigDecimal.valueOf(100));
    }
    
    /**
     * 
     * 功能描述: 得到完成率 = (A完成台数/A任务台数)*0.6+(B完成台数/B任务台数)*0.4<br>
     *
     * @param item
     * @return
     */
    private BigDecimal getCompleteRate(BiAreaTaskProgressVo item){
        Integer targetNumA = item.getTargetNumA();
        Integer targetNumB = item.getTargetNumB();
        Integer saleNumA = item.getSaleNumA();
        Integer saleNumB = item.getSaleNumB();
        BigDecimal rateA = (null == targetNumA || targetNumA == 0 || null == saleNumA) ? BigDecimal.ZERO 
                : BigDecimal.valueOf(saleNumA).divide(BigDecimal.valueOf(targetNumA), 3, BigDecimal.ROUND_HALF_UP).multiply(BigDecimal.valueOf(0.6));
        BigDecimal rateB = (null == targetNumB || targetNumB == 0 || null == saleNumB) ? BigDecimal.ZERO 
                : BigDecimal.valueOf(saleNumB).divide(BigDecimal.valueOf(targetNumB), 3, BigDecimal.ROUND_HALF_UP).multiply(BigDecimal.valueOf(0.4));
        return BigDecimalUtils.halfUpThreeDecimal(rateA.add(rateB)).multiply(BigDecimal.valueOf(100));
    }
    
    private BigDecimal defaultZero(BigDecimal value) {
        return value = null == value ? BigDecimal.ZERO : value;
    }

    private Integer defaultZero(Integer value) {
        return value = null == value ? NumberUtils.INTEGER_ZERO : value;
    }
    
    private BiAreaTaskProgressVo getEmptyTotalTaskProgress(HqTask hqTask){
        BiAreaTaskProgressVo value = new BiAreaTaskProgressVo();
        value.setDisCode("00000");
        value.setDisName("全部");
        value.setSaleNumA(NumberUtils.INTEGER_ZERO);
        value.setSaleAmountA(BigDecimal.ZERO);
        value.setSaleNumB(NumberUtils.INTEGER_ZERO);
        value.setSaleAmountB(BigDecimal.ZERO);
        value.setSaleNumB2(NumberUtils.INTEGER_ZERO);
        value.setSaleAmountB2(BigDecimal.ZERO);
        value.setTargetNumA(NumberUtils.INTEGER_ZERO);
        value.setTargetNumB(NumberUtils.INTEGER_ZERO);
        value.setCompleteRate(BigDecimal.ZERO);
        value.setSaleRate(BigDecimal.ZERO);
        value.setCateSaleAmount(defaultZero(mainPushTaskHqViewDao.selectCateSaleAmountByCode(hqTask.getCateCode(), 
                hqTask.getMonth(), StringUtils.EMPTY)));
        return value;
    }
    
}
